package com.bee.auth.service.impl;

import com.bee.auth.client.AuthHolder;
import com.bee.auth.client.util.HttpSecurityUtil;
import com.bee.auth.manager.UserManager;
import com.bee.auth.common.vo.UserVO;
import com.bee.auth.service.AuthService;
import com.bee.auth.service.LoginService;
import com.bee.commons.utils.Md5Util;
import com.bee.commons.utils.ShaUtil;
import com.bee.user.client.dto.UserDTO;
import com.bee.user.client.enums.UserTypeEnum;
import com.google.common.collect.Maps;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.stereotype.Service;

import java.util.Calendar;
import java.util.Map;

/**
 * @author Damin.yang
 * @date 2019/08/23 16:51
 */
@Slf4j
@RefreshScope
@Service
public class LoginServiceImpl implements LoginService {

    @Value("${auth.jwt.signingKey}")
    private String secretKey;
    /**
     * 单位：分钟
     */
    @Value("${auth.jwt.expireTime}")
    private int expireTime;

    @Autowired
    private UserManager userManager;

    @Autowired
    private AuthService authService;

    @Override
    public UserVO login(String user, String password) {
        UserDTO dto = userManager.queryUserByUsernameOrPhone(user);
        if (dto == null) {
            throw new RuntimeException("用户不存在");
        }

        if (!dto.getPassword().equals(cryptPassword(password, dto.getSalt()))) {
            throw new RuntimeException("密码错误");
        }

        if (!dto.getEnable()) {
            throw new RuntimeException("用户已禁用");
        }

        UserVO vo = UserVO.convert(dto);

        Calendar expire = Calendar.getInstance();
        expire.add(Calendar.MINUTE, expireTime);
        String token = HttpSecurityUtil.createJwtToken(generateLoginContext(dto), secretKey, expire.getTime());
        vo.setToken(token);

        // 后台用户，则加载后台菜单
        if (vo.getType() == UserTypeEnum.MANAGEMENT.ordinal()) {
            authService.loadUserResource(vo.getId(), expireTime * 60, dto.getRoles());
        }

        return vo;
    }

    private Map<String, Object> generateLoginContext(UserDTO dto) {
        Map<String, Object> map = Maps.newHashMap();
        map.put(AuthHolder.USER_ID, dto.getId());
        map.put(AuthHolder.NAME, dto.getName());
        map.put(AuthHolder.USERNAME, dto.getUsername());
        map.put(AuthHolder.PHONE, dto.getPhone());
        map.put(AuthHolder.TYPE, dto.getType());
        map.put(AuthHolder.ORG_ID, dto.getOrgId());
        map.put(AuthHolder.ROLES, dto.getRoles());
        return map;
    }


    @Override
    public String cryptPassword(String password, String salt) {
        return Md5Util.md5(ShaUtil.sha1(password + salt), salt);
    }
}
